<?php
class Solution {

    /**
     * @param String $s
     * @return Integer
     */
    function calculate($s) {
        // 去空格
        $s = str_replace(" ", "", $s);

        $stack = array();
        $len = strlen($s);

        // 跟踪前一个操作符
        $pre = ' ';

        // 字符串处理一遍即可
        for ($i=0; $i<$len; $i++) {
            // 操作数  数字拼起来 【因为整数可能不止一位，这个地方要注意把整数取完整】
            $num = 0;
            while ($i<$len && is_numeric($s[$i])) {
                $num = $num * 10 +  $s[$i];
                $i++;
            };

            // 查看其前一个运算符分情况讨论
            switch ($pre) {
                case '+':
                    array_unshift($stack, $num);
                    break;
                case '-':
                    // 把减法全换成加法统一处理
                    array_unshift($stack, -$num);
                    break;
                case '*':
                    // 乘法除法优先级高先处理, 取出栈顶元素，和当前操作数计算后，再次入栈
                    array_unshift($stack, array_shift($stack) * $num);
                    break;
                case '/':
                    // 乘法除法优先级高先处理, 取出栈顶元素，和当前操作数计算后，再次入栈
                    array_unshift($stack, intval(array_shift($stack) / $num));
                    break;
                default:
                    // 默认入栈 【主要是第一个操作数使用】
                    array_unshift($stack, $num);
                    break;
            }

            // 更新前一个操作符
            if ($i < $len) {
                // 因为每一次数字都是直接取完的  所以下一个一定是操作符
                $pre = $s[$i];
            }

            // 注意每一次for循环还好执行一次$i++ 所以每次for循环里面的第一次$s[$i]一定是数字
        }

        // 对栈里面剩下的元素求和
        return array_sum($stack);
    }
}

var_dump((new Solution())->calculate('300+2*2'));